﻿//===============================================================================
// Apolineo Patterns & Practices LeanEngine Framework
//===============================================================================
// Copyright © Apolineo Desenvolvimento de Sistemas Ltda.  All rights reserved.
// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY
// OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT
// LIMITED TO THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
// FITNESS FOR A PARTICULAR PURPOSE.
//===============================================================================

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.Linq.Mapping;

using LeanEngine.Entity;
using LeanEngine.Validation;
using LeanEngine.SalesConcept.Validator;
using LeanEngine.SalesConcept.Business;

namespace LeanEngine.SalesConcept.Entity
{
    //O atributo Table do namespace System.Data.Linq.Mapping é responsável
    //por informar ao lob que a classe se refere a tabela
    //'Customer' no banco de dados

    //Herdamos da classe DataTransferObject para o lob gerencie as mudanças
    //nos valores das propriedades, faça atualizações pessimistas e envie
    //no comando update somente os dados alterados, além do, versionamento
    //do dado automaticamente
    [Table(Name = "Customer")]
    public class Customer : ChangeTrackerEntity, IPerson
    {
        #region ITransferObject Members

        //Aqui mapeamos a coluna PK da tabela Customer e informamos ao lob
        //que o valor dela é gerado pelo banco de dados
        [Column(Name = "CustomerId", IsPrimaryKey = true, IsDbGenerated = true)]
        public long Id
        {
            get;
            set;
        }

        #endregion

        #region IPerson Members

        //Aqui mapeamos a coluna 'Name' e adicionamos um validador para
        //assegurar que seja preenchido, e em
        //caso de erro, lança uma exceção de negócio com a mensagem de erro
        //obtida através do resource 'ErrorMessages', chave 'PersonNameRequired'
        [IsNotEmpty(typeof(ErrorMessages), "PersonNameRequired"),
        Column(Name = "Name")]
        public string Name
        {
            get;
            set;
        }

        //Aqui mapeamos a coluna 'DocumentNumber' e adicionamos nossa validação
        //customizada para verificar que, quando preenchido, represente um
        //número válido de cpf, e em
        //caso de erro, lança uma exceção de negócio com a mensagem de erro
        //obtida através do resource 'ErrorMessages', chave 'PersonDocumentNumberRequired'
        [IsNotEmpty(typeof(ErrorMessages), "PersonDocumentNumberRequired"),
        IsEmptyOrValidCPF(typeof(ErrorMessages), "InvalidCPF"),
        Column(Name = "DocumentNumber")]
        public string DocumentNumber
        {
            get;
            set;
        }

        //Aqui mapeamos a coluna 'Birthdate' e adicionamos uma validação padrão
        //para assegurar que a data de nascimento seja preenchida, e em
        //caso de erro, lança uma exceção de negócio com a mensagem de erro
        //obtida através do resource 'ErrorMessages', chave 'PersonBirthDateInvalid
        [IsNotDefaultDate(typeof(ErrorMessages), "PersonBirthDateInvalid"),
        Column(Name = "Birthdate")]
        public DateTime Birthdate
        {
            get;
            set;
        }

        #endregion

        #region Customer Members

        //Aqui mapeamos a coluna 'Address' e adicionamos uma validação padrão
        //para assegurar que o endereço seja preenchido, e em
        //caso de erro, lança uma exceção de negócio com a mensagem de erro
        //obtida através do resource 'ErrorMessages', chave 'CustomerAddressRequired
        [IsNotEmpty(typeof(ErrorMessages), "CustomerAddressRequired"),
        Column(Name = "Address")]
        public string Address
        {
            get;
            set;
        }

        //Aqui mapeamos a coluna 'Email' e adicionamos uma validação customizada
        //para assegurar que o e-mail seja válido (quando preenchido), e em
        //caso de erro, lança uma exceção de negócio com a mensagem de erro
        //obtida através do resource 'ErrorMessages', chave 'InvalidEmail
        [IsEmptyOrEmailAttribute(typeof(ErrorMessages), "InvalidEmail"),
        Column(Name = "Email")]
        public string Email
        {
            get;
            set;
        }

        #endregion

        #region Overrided Members

        public override string ToString()
        {
            return this.Name;
        }

        #endregion
    }
}